package com.diandi.messages.tools;


import com.diandi.messages.enums.ReturnCode;
import com.diandi.messages.properties.MessagePlatformProperties;
import com.diandi.messages.sign.SignUtil;
import org.apache.commons.lang3.StringUtils;

import javax.servlet.http.HttpServletRequest;
import java.io.*;
import java.net.URLDecoder;
import java.net.URLEncoder;
import java.security.MessageDigest;
import java.util.*;
import java.util.zip.ZipEntry;
import java.util.zip.ZipOutputStream;

public class Tools {
    //签名版本
    public static final String SIGN_VERSION_NAME = "sign_version";

    //签名类型
    public static final String SIGN_TYPE_NAME = "sign_type";

    //签名值
    public static final String SIGN_NAME = "sign";

    /**
     * 创建http post发送数据的url连接
     *
     * @param params 转换数据 map
     * @param encode 是否做urlencode
     * @return url
     */
    public static String createLinkString(Map<String, String> params, boolean encode) {
        List<String> keys = new ArrayList<String>(params.keySet());
        Collections.sort(keys);
        String prestr = "";
        String charset = "UTF-8";
        for (int i = 0; i < keys.size(); i++) {
            String key = keys.get(i);
            String value = params.get(key) == null ? "" : params.get(key);
            if (encode) {
                try {
                    value = URLEncoder.encode(value, charset);
                } catch (UnsupportedEncodingException e) {
                    e.printStackTrace();
                }
            }
            if (i == keys.size() - 1) {
                prestr = prestr + key + "=" + value;
            } else {
                prestr = prestr + key + "=" + value + "&";
            }
        }

        return prestr;
    }
    /**
     * 创建发送业务端http post发送数据的url连接
     *
     * @param params 转换数据 map
     * @param encode 是否做urlencode
     * @return url
     */
    public static String createBusinessLinkString(Map<String, String> params, boolean encode, String charset) {
        List<String> keys = new ArrayList<String>(params.keySet());
        Collections.sort(keys);
        String prestr = "";
        for (int i = 0; i < keys.size(); i++) {
            String key = keys.get(i);
            String value = params.get(key);
            if (encode) {
                try {
                    value = URLEncoder.encode(value, charset);
                } catch (UnsupportedEncodingException e) {
                    e.printStackTrace();
                }
            }
            if (i == keys.size() - 1) {
                prestr = prestr + key + "=" + value;
            } else {
                prestr = prestr + key + "=" + value + "&";
            }
        }

        return prestr;
    }

    /**
     * url解码
     * @param params 转换数据 map
     * @param charset  编码格式
     * @param decode 是否做urldecode
     * @return url
     */
    public static String MapTransfStringByDecode(Map<String, String> params, String charset, boolean decode) {
        List<String> keys = new ArrayList<String>(params.keySet());
        Collections.sort(keys);
        String prestr = "";
        for (int i = 0; i < keys.size(); i++) {
            String key = keys.get(i);
            String value = params.get(key);
            if (decode) {
                try {
                    value = URLDecoder.decode(value,charset);
                } catch (UnsupportedEncodingException e) {
                    e.printStackTrace();
                }
            }
            if (i == keys.size() - 1) {
                prestr = prestr + key + "=" + value;
            } else {
                prestr = prestr + key + "=" + value + "&";
            }
        }

        return prestr;
    }




    public static Map getParameterMap(HttpServletRequest request, boolean isFilter) {
        // 参数Map
        Map properties = request.getParameterMap();
        // 返回值Map
        Map returnMap = new HashMap();
        Iterator entries = properties.entrySet().iterator();
        Map.Entry entry;
        String name = "";
        String value = "";
        while (entries.hasNext()) {
            entry = (Map.Entry) entries.next();
            name = (String) entry.getKey();
            if (isFilter) {
                if (!name.equals("sign") && !name.equals("sign_type") && !name.equals("sign_version") && !name.equals("url")) {
                    Object valueObj = entry.getValue();
                    if (null == valueObj) {
                        value = "";
                    } else if (valueObj instanceof String[]) {
                        String[] values = (String[]) valueObj;
                        for (int i = 0; i < values.length; i++) {
                            value = values[i] + ",";
                        }
                        value = value.substring(0, value.length() - 1);
                    } else {
                        value = valueObj.toString();
                    }
                    returnMap.put(name, value);
                }
            } else {
                Object valueObj = entry.getValue();
                if (null == valueObj) {
                    value = "";
                } else if (valueObj instanceof String[]) {
                    String[] values = (String[]) valueObj;
                    for (int i = 0; i < values.length; i++) {
                        value = values[i] + ",";
                    }
                    value = value.substring(0, value.length() - 1);
                } else {
                    value = valueObj.toString();
                }
                /*if (isNull) {//判断参数的值是否为空
                    if (StringUtils.isBlank(value)) {
                        returnMap.clear();
                        returnMap.put("error", name);
                        return returnMap;
                    }
                }*/
                returnMap.put(name, value);
            }
        }
        return returnMap;
    }

    /**
     * 计算文件的MD5摘要值
     *
     * @param file 文件路劲
     * @return 32位的MD5摘要
     */
    public static String getFileMD5(File file) {
        if (!file.isFile()) {
            return null;
        }
        MessageDigest digest = null;
        FileInputStream in = null;
        byte buffer[] = new byte[1024];
        int len;
        try {
            digest = MessageDigest.getInstance("MD5");
            in = new FileInputStream(file);
            while ((len = in.read(buffer, 0, 1024)) != -1) {
                digest.update(buffer, 0, len);
            }
            in.close();
        } catch (Exception e) {
            e.printStackTrace();
            return null;
        }
        String bytes2hex03 = bytes2hex03(digest.digest());
        return bytes2hex03;

    }

    public static String bytes2hex03(byte[] bytes) {
        final String HEX = "0123456789abcdef";
        StringBuilder sb = new StringBuilder(bytes.length * 2);
        for (byte b : bytes) {
            // 取出这个字节的高4位，然后与0x0f与运算，得到一个0-15之间的数据，通过HEX.charAt(0-15)即为16进制数  
            sb.append(HEX.charAt((b >> 4) & 0x0f));
            // 取出这个字节的低位，与0x0f与运算，得到一个0-15之间的数据，通过HEX.charAt(0-15)即为16进制数  
            sb.append(HEX.charAt(b & 0x0f));
        }

        return sb.toString();
    }


    /*
     * 交易类网关列表，用于判断请求网关地址
     */
    public static String[][] get_trade_Interface_service() {
        String[][] trade_Interface_service =
                {
                        {"create_hosting_collect_trade", "创建托管代收交易"},
                        {"create_single_hosting_pay_trade", "创建托管代付交易"},
                        {"create_batch_hosting_pay_trade", "创建批量托管代付交易"},
                        {"pay_hosting_trade", "托管交易支付"},
                        {"query_pay_result", "支付结果查询"},
                        {"query_hosting_trade", "托管交易查询"},
                        {"query_hosting_batch_trade", "托管交易批次查询"},
                        {"create_hosting_refund", "托管退款"},
                        {"query_hosting_refund", "托管退款查询"},
                        {"create_hosting_deposit", "托管充值"},
                        {"query_hosting_deposit", "托管充值查询"},
                        {"create_hosting_withdraw", "托管提现"},
                        {"query_hosting_withdraw", "托管提现查询"},
                        {"create_hosting_transfer", "转账接口"},
                        {"advance_hosting_pay", "支付推进"},
                        {"create_bid_info", "标的录入"}, {"query_bid_info", "标的信息查询"},
                        {"create_single_hosting_pay_to_card_trade", "创建单笔代付到提现卡交易"},
                        {"create_batch_hosting_pay_to_card_trade", "创建批量代付到提现卡交易"},
                        {"finish_pre_auth_trade", "代收完成"},
                        {"cancel_pre_auth_trade", "代收撤销"},
                        {"query_fund_yield", "5.1存钱罐基金收益率查询"}
                };
        return trade_Interface_service;
    }

    public static String[] get_need_RSA() {
        String[] array = {"real_name", "cert_no", "verify_entity", "bank_account_no", "account_name",
                "phone_no", "validity_period", "verification_value", "telephone", "email", "organization_no",
                "legal_person", "legal_person_phone", "agent_name", "license_no", "agent_mobile"};

        return array;
    }

    // 传入service_name，返回web端的服务器地址
    public static String get_url(String service_name) {
        String wpay_url = null;
        outterLoop:
        for (String[] strs : get_trade_Interface_service()) {
            for (String str : strs) {
                if (str.toString().equals(service_name)) {
                    wpay_url = "https://testgate.pay.sina.com.cn/mas/gateway.do";// 网管地址 此处为测试订单类接口地址，请根据实际情况填写
                    break outterLoop;
                } else {
                    wpay_url = "https://testgate.pay.sina.com.cn/mgs/gateway.do";// 网管地址 此处为测试会员类接口地址，请根据实际情况填写
                }
            }
        }
        return wpay_url;
    }


    /**
     * 一次性压缩多个文件，文件存放至一个文件夹中
     */
    public static void ZipMultiFile(String filepath, String zippath) {
        try {
            File file = new File(filepath);// 要被压缩的文件夹
            File zipFile = new File(zippath);
            InputStream input = null;
            ZipOutputStream zipOut = new ZipOutputStream(new FileOutputStream(zipFile));
            if (file.isDirectory()) {
                File[] files = file.listFiles();
                for (int i = 0; i < files.length; ++i) {
                    input = new FileInputStream(files[i]);
                    zipOut.putNextEntry(new ZipEntry(file.getName() + File.separator + files[i].getName()));
                    int temp = 0;
                    while ((temp = input.read()) != -1) {
                        zipOut.write(temp);
                    }
                    input.close();
                }
            }
            zipOut.close();
        } catch (Exception e) {
            e.printStackTrace();
        }
    }


    /***
     * 去掉字符串前后的空格，中间的空格保留
     * @param str
     * @return
     */
    public static String trimInnerSpaceStr(String str) {
        str = str.trim();
        while (str.startsWith(" ")) {
            str = str.substring(1, str.length()).trim();
        }
        while (str.endsWith(" ")) {
            str = str.substring(0, str.length() - 1).trim();
        }


        return str;
    }

    /**
     * 生成公用的返回业务端参数
     *
     * @param returnCode
     * @param desc 新浪处理描述
     * @param params
     * @return
     */
    public static Map<String, String> createReturnParams(ReturnCode returnCode, String desc, String params) {
        Map<String, String> returnMap = new HashMap<String, String>();
        returnMap.put("code", returnCode.getCode());
        returnMap.put("msg", returnCode.getMsg());
        if (StringUtils.isNotBlank(desc))returnMap.put("desc", desc);
        if (StringUtils.isNotBlank(params)) returnMap.put("errorParam", params);
        returnMap.put("_input_charset", "UTF-8");
        return returnMap;
    }

    /**
     * 申请ca使用返回错误信息
     *
     * @param returnCode
     * @param desc 新浪处理描述
     * @param params
     * @return
     */
/*    public static Map<String, String> createCAReturnParams(ReturnCode returnCode, String desc, String params) {
        Map<String, String> returnMap = new HashMap<String, String>();
        returnMap.put("code", returnCode.getCode());
        returnMap.put("msg", returnCode.getMsg());
        if (StringUtils.isNotBlank(desc))returnMap.put("desc", desc);
        if (StringUtils.isNotBlank(params)) returnMap.put("errorParam", params);
        returnMap.put("_input_charset", "UTF-8");
        return returnMap;
    }*/



    /**
     * 签名验证(对业务端进行签名认证)
     * @param request
     * @param messagePlatformProperties
     * @param type
     * @return
     */
    public static Map<String, String> checkBusinessSign(HttpServletRequest request, MessagePlatformProperties messagePlatformProperties, String type) {
        Map<String, String> requestMap = Tools.getParameterMap(request, false);
        Map<String, String> returnMap = new HashMap<String, String>();
        try {
            if ("platfrom".equals(type)) {
                returnMap = SignUtil.verifyBusinessCallBack(requestMap, messagePlatformProperties.getPayPublicSign(requestMap.get("merchantNo")), messagePlatformProperties.getCharset(),messagePlatformProperties.getPaySignType());
            }else if ("sina".equals(type)) {
                //returnMap = SignUtil.verifyBusinessCallBack(requestMap, sinaProperties.getRsaPublicSignKey(), null,null);
            }
        } catch (Exception e) {
            e.printStackTrace();
            returnMap.put("error","签名校验失败");
        }
        return returnMap;
    }

}
